package com.lengxf.aPlugins.entity;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import io.swagger.v3.oas.annotations.media.Schema;

import java.lang.reflect.Field;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;

public interface SqlGenerator {

    String pathPrefix = "../../1-sql";

    String INSERT_MODEL_STR = "insert into %s ( %s ) values ( %s );" + "\n";

    String DELETE_SQL = "delete from %s where id >= %s and id < %s;" + "\n";

    default void generate() {
        Schema annotation = this.getClass().getAnnotation(Schema.class);
        String tableName = annotation.description();
        List<String> columnNameList = new ArrayList<>();
        List<Object> columnValueList = new ArrayList<>();
        Field[] declaredFields = this.getClass().getDeclaredFields();
        try {
            for (Field declaredField : declaredFields) {
                declaredField.setAccessible(true);
                String columnName = declaredField.getAnnotation(Schema.class).description();
                columnNameList.add(columnName);
                Object value = declaredField.get(this);
                columnValueList.add(value);
            }
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        String columnInsert = StrUtil.join(" , ", columnNameList);
        String columnValueInsert = StrUtil.join(" , ", buildInsertValueList(columnValueList));
        String sql = String.format(INSERT_MODEL_STR, tableName, columnInsert, columnValueInsert);
        FileUtil.appendUtf8String(sql, pathPrefix + "/" + tableName + ".sql");
    }

    default void generateDeleteSql(long minId, long maxId) {
        Schema annotation = this.getClass().getAnnotation(Schema.class);
        String tableName = annotation.description();
        String sql = String.format(DELETE_SQL, tableName, minId, maxId);
        FileUtil.appendUtf8String(sql, pathPrefix + "/" + "DeleteData(" + minId + "-" + maxId + ").sql");
    }

    static List<String> buildInsertValueList(List<Object> columnValueList) {
        List<String> insertValueList = new ArrayList<>();
        for (Object columnValue : columnValueList) {
            if (columnValue instanceof LocalDateTime) {
                insertValueList.add(String.format("TIMESTAMP '%s'", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss").format((LocalDateTime) columnValue)));
            }
            if (columnValue instanceof Number) {
                insertValueList.add(String.valueOf(columnValue));
            }
            if (columnValue instanceof String) {
                insertValueList.add(String.format("'%s'", columnValue));
            }
            if (ObjectUtil.isNull(columnValue)) {
                insertValueList.add("NULL");
            }
        }
        return insertValueList;
    }


}
